#include "./handles.hpp"
#include <iostream>

namespace qbe::input {

// Mouse相关事件
void HandleBundle::apply(vsg::ButtonPressEvent& e) {
  if (!*enable)
    return;
  mouse_press = true;
  mouse_press_event = &e;
  mouse_press_events.push_back(&e);
}
void HandleBundle::apply(vsg::ButtonReleaseEvent& e) {
  if (!*enable)
    return;
  mouse_release = true;
  mouse_release_event = &e;
  mouse_release_events.push_back(&e);
}

void HandleBundle::apply(vsg::MoveEvent& e) {
  if (!*enable)
    return;
  mouse_move = true;
  move_event = &e;
}

void HandleBundle::apply(vsg::ScrollWheelEvent& e) {
  if (!*enable)
    return;
  mouse_wheel = true;
  mouse_wheel_event = &e;
}

// Window相关事件
void HandleBundle::apply(vsg::ConfigureWindowEvent& e) {
  if (!*enable)
    return;
  window_resize = true;
  window_resize_event = &e;
};

void HandleBundle::apply(vsg::CloseWindowEvent& e) {
  if (!*enable)
    return;
  window_close = true;
  window_close_event = &e;
};

// Key相关事件
void HandleBundle::apply(vsg::KeyPressEvent& e) {
  // std::cout << "Enbale : " << *enable << " Event : " << e.keyBase << std::endl;
  if (!*enable)
    return;
  key_press = true;
  key_press_event = &e;
  key_press_events.push_back(&e);
}

void HandleBundle::apply(vsg::KeyReleaseEvent& e) {
  if (!*enable)
    return;
  // key_release = true;
  // key_release_event = &e;
}

void HandleBundle::getGlobalKeyEvent(vsg::KeyReleaseEvent& e) {
  if (!*enable)
    return;
  key_release = true;
  key_release_event = &e;
  key_release_events.push_back(&e);
}

bool HandleBundle::keyPressed(vsg::KeySymbol key_symbol) {
  if (!*enable)
    return false;
  // SPDLOG_INFO("keyPressed:");
  if (key_press) {
    for (auto event : key_press_events) {
      if (key_symbol == event->keyBase) {
        return true;
      }
    }
  }
  return false;
}

// 检测快捷键是否按下
bool HandleBundle::keyPressed(const KeyBoardShortcuts& kbs) {
  if (!*enable)
    return false;
  // SPDLOG_INFO("keyPressed:");
  if (key_press) {
    if (kbs.keyModifier != key_press_event->keyModifier)
      return false;

    // 非字符基础键
    if ((int)kbs.keyBase < 'a' && (int)kbs.keyBase > 'z' && (int)(int)kbs.keyBase < 'A' && (int)kbs.keyBase > 'Z')
      return kbs.keyBase == key_press_event->keyBase;

    // 字符基础键不区分大小写
    if ((int)kbs.keyBase <= 'z')
      return (kbs.keyBase == key_press_event->keyBase) || (kbs.keyBase + 32 == key_press_event->keyBase);
    else
      return (kbs.keyBase == key_press_event->keyBase) || (kbs.keyBase - 32 == key_press_event->keyBase);
  }
  return false;
}

bool HandleBundle::keyReleased(const KeyBoardShortcuts& kbs) {
  if (!*enable)
    return false;
  // SPDLOG_INFO("keyPressed:");
  if (key_release) {
    if (kbs.keyModifier != key_release_event->keyModifier)
      return false;

    // 非字符基础键
    if ((int)kbs.keyBase < 'a' && (int)kbs.keyBase > 'z' && (int)(int)kbs.keyBase < 'A' && (int)kbs.keyBase > 'Z')
      return kbs.keyBase == key_release_event->keyBase;

    // 字符基础键不区分大小写
    if ((int)kbs.keyBase <= 'z')
      return (kbs.keyBase == key_release_event->keyBase) || (kbs.keyBase + 32 == key_release_event->keyBase);
    else
      return (kbs.keyBase == key_release_event->keyBase) || (kbs.keyBase - 32 == key_release_event->keyBase);
  }
  return false;
}

bool HandleBundle::keyReleased(vsg::KeySymbol key_symbol) {
  if (!*enable)
    return false;
  if (key_release) {
    for (auto event : key_release_events) {
      if (key_symbol == event->keyBase) {
        return true;
      }
    }
  }
  return false;
}

bool HandleBundle::mouseMoved(int32_t* x, int32_t* y) {
  if (!*enable)
    return false;
  if (mouse_move) {
    *x = move_event->x;
    *y = move_event->y;
    // SPDLOG_INFO("mouse: {}, {}", *x, *y);
    return true;
  }
  return false;
}

bool HandleBundle::mousePressed(vsg::ButtonMask mask) {
  if (!*enable)
    return false;
  if (mouse_press) {
    for (auto event : mouse_press_events) {
      if (mask & event->mask) {
        return true;
      }
    }
  }
  return false;
}

bool HandleBundle::mouseReleased(vsg::ButtonMask mask) {
  if (!*enable)
    return false;
  if (mouse_release) {
    for (auto event : mouse_release_events) {
      if (mask & event->mask) {
        return true;
      }
    }
  }
  return false;
}

bool HandleBundle::mouseReleased(uint32_t button) {
  if (!*enable)
    return false;
  if (mouse_release) {
    return button == mouse_release_event->button;
  }
  return false;
}

bool HandleBundle::mouseWheel(int* delta_y) {
  if (!*enable)
    return false;
  if (mouse_wheel) {
    *delta_y = mouse_wheel_event->delta.y;
    return true;
  }
  return false;
}

bool HandleBundle::resized(uint32_t* x, uint32_t* y, uint32_t* width, uint32_t* height) {
  if (!*enable)
    return false;

  if (window_resize) {
    *x = window_resize_event->x;
    *y = window_resize_event->y;
    *width = window_resize_event->width + 16;
    *height = window_resize_event->height + 39;
    return true;
  }
  return false;
}

void HandleBundle::reset() {
  mouse_move = false;
  mouse_press = false;
  mouse_release = false;
  mouse_wheel = false;

  window_resize = false;

  key_press = false;
  key_release = false;

  key_press_event = nullptr;
  key_release_event = nullptr;

  key_press_events.clear();
  key_release_events.clear();

  mouse_press_events.clear();
  mouse_release_events.clear();
}

}  // namespace qbe::input
